package com.liangtian.mdm.dm.listener;

import com.liangtian.mdm.dm.common.constant.TableConst;
import com.liangtian.mdm.dm.common.enums.Style;
import com.liangtian.mdm.dm.config.dao.AttrConfigDao;
import com.liangtian.mdm.dm.config.model.AttrConfig;
import com.liangtian.mdm.dm.model.dao.ModelDao;
import com.liangtian.mdm.dm.model.model.Model;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;

import java.util.*;

@SuppressWarnings({"unchecked"})
@Repository
public class CacheUtil {

    @Autowired
    private ModelDao modelDao;

    @Autowired
    private AttrConfigDao attrConfigDao;

    /**
     * 获取模型
     */
    public Model getModel(String modelId) {
        Model model = null;
        try {
            model = Ehcache.getCache().getModelCache().get(modelId);
            if (model == null) {
                model = modelDao.selectValidModel(modelId);
                Ehcache.getCache().getModelCache().put(modelId, model);
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return model;
    }

    /**
     * 查询给定模型ID的子模型
     * @param modelId
     * @return
     */
/*
	public Model getSubModel(String modelId){
		Model model = null;
		try{
//			model = Ehcache.getCache().getModelCache().get(modelId);
//			if(model==null){
//				model = modelDao.selectValidModel(modelId);
//				Ehcache.getCache().getModelCache().put(modelId, model);
//			}
//			if(!"0".equals(model.getClassType())){
//				model = null ;
//			}
			Cache<String, Model> models = Ehcache.getCache().getModelCache();
			for(String id : models.){
				
			}
		}catch(Exception e){
			e.printStackTrace();
		}
		return model;
	}
*/

    /**
     * 用于insert变更、分发、历史的sql中
     * 直接获模型的数据库列
     */
    //@Deprecated
    public String getColumns(String modelId) {
        String cols = null;
        try {
            cols = Ehcache.getCache().getColumnsCache().get(modelId);
            if (cols == null) {
                cols = ",";
                Map<String, AttrConfig> ma = this.getAttrMap(modelId);
                for (AttrConfig ac : ma.values()) {
                    if (ac.getDataType() != null && ac.getDataType().endsWith("BLOB")) {
                        continue;
                    } else {
                        cols += ac.getAttrColumn() + ",";
                    }
                }
                cols = cols.substring(1);
                Ehcache.getCache().getColumnsCache().put(modelId, cols);
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return cols;
    }

    /**
     * 用于select的sql语句，替换getColumns
     * 获取给定模型的列，转义select、checkbox等组件列的显示值
     *
     * @param modelId
     */
    public String getQueryColumns(String modelId) {
        String cols = null;
        try {
            cols = Ehcache.getCache().getQueryColsCache().get(modelId);
            if (cols == null) {
                cols = ",";
                Map<String, AttrConfig> ma = this.getAttrMap(modelId);
                for (AttrConfig ac : ma.values()) {
                    cols += getColFullInfoByAttrConfigInfo(ac);
                }
                cols = cols.substring(1);
                Ehcache.getCache().getQueryColsCache().put(modelId, cols);
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return cols;
    }

    //wy
    public String getColFullInfoByAttrConfigInfo(AttrConfig ac) {
        String col = "";

        String attrType = ac.getAttrType();
        if (Style.VARCHAR2.getCode().equals(attrType) || Style.NUMBER.getCode().equals(attrType)
                || Style.MAIL.getCode().equals(attrType) || Style.HIDE.getCode().equals(attrType)
                || Style.DATE.getCode().equals(attrType) || Style.NUMBERM.getCode().equals(attrType)
                || Style.CLOB.getCode().equals(attrType)) {
            col = ac.getAttrColumn() + ",";
        } else if (Style.BLOB.getCode().equals(attrType)) {

        } else {
            // 关联表
            String relateTable = TableConst.TABLEPREFIX + ac.getDataSourceTable();
            // 显示列
            String showCol = ac.getDataSourceShowColumn();
            //if(Style.LISTTREE.getCode().equals(attrType) && (ac.getIsParentType()==1)){ //父子树
            if (Style.LISTTREE.getCode().equals(attrType) && (ac.getIsDefaultParentType() == 1)) { //父子树
                col = "(SELECT " + relateTable + "." + showCol + " from " + relateTable + " " + relateTable
                        + " where id = t." + ac.getAttrColumn() + " ) " + ac.getAttrColumn() + ",";
                //	cols += "(SELECT "+relateTable+"."+ showCol +" from "+relateTable+" "+relateTable +" where id = t.pid) " + ac.getAttrColumn()  +",";
            } else if (Style.CHECKBOX.getCode().equals(attrType)) { //复选框
                col = "(select wmsys.wm_concat(" + relateTable + "." + showCol + ") from " + relateTable + " " + relateTable
                        + " where id in (select column_value from (table(fn_split(t." + ac.getAttrColumn() + ", ',')))) group by null) " + ac.getAttrColumn() + ",";
            } else if (Style.POPLIST.getCode().equals(attrType)) {
                if ("5".equals(ac.getModuleType())) {//表示外部引用表，非动态模型生成的表
                    col = ac.getAttrColumn() + ",";
                } else {
                    col = "(SELECT " + relateTable + "." + showCol + " from " + relateTable + " " + relateTable
                            + " where id = t." + ac.getAttrColumn() + " ) " + ac.getAttrColumn() + ",";
                }
            } else {
                col = "(SELECT " + relateTable + "." + showCol + " from " + relateTable + " " + relateTable
                        + " where id = t." + ac.getAttrColumn() + " ) " + ac.getAttrColumn() + ",";
            }
        }

        return col;
    }

    /**
     * 获取给定模型的 属性List集合
     *
     * @param modelId
     * @return 排序规则：model_id, show_order, group_id nulls last, group_order, attr_id
     */
    public List<AttrConfig> getAttrList(String modelId) {
        List<AttrConfig> attrList = null;
        try {
            LinkedHashMap<String, AttrConfig> ma = (LinkedHashMap<String, AttrConfig>) Ehcache.getCache().getAttrConfigCache().get(modelId);
//			HashMap<String, AttrConfig> ma = Ehcache.getCache().getAttrConfigCache().get(modelId);
            if (null == ma || 0 == ma.size()) {
//				ma = new HashMap<String, AttrConfig>();
                ma = new LinkedHashMap<String, AttrConfig>();
                Map<String, String> cond = new HashMap<>();
                cond.put("modelId", modelId);
                attrList = attrConfigDao.queryValidAttributeList(cond);
                for (AttrConfig ac : attrList) {
                    ma.put(ac.getAttrColumn(), ac);
                }
                Ehcache.getCache().getAttrConfigCache().put(modelId, ma);
            } else {
                attrList = new ArrayList<AttrConfig>();
                for (AttrConfig ac : ma.values()) {
                    attrList.add(ac);
                }
            }
            // 屬性排序 (先按列表，然后按组，然后按组内顺序，然后按属性添加先后)
//			Collections.sort(attrList, new java.util.Comparator<AttrConfig>(){
//				@Override
//				public int compare(AttrConfig o1, AttrConfig o2) {
//					int sort = o1.getShowOrder() - o2.getShowOrder(); //系统设有默认值
//					if(sort==0){
//						if(o1.getGroupId()==null)
//							sort = o2.getGroupId()==null ? -1 : 1;
//						else if(o2.getGroupId()==null)
//							sort = -1;
//						else
//							sort = o1.getGroupId().compareTo(o2.getGroupId());
//							if(sort==0)
//								sort = o1.getGroupOrder() - o2.getGroupOrder();
//								if(sort==0)
//									sort = o1.getAttrId().compareTo(o2.getAttrId());
//					}
//					return sort;
//				}
//			});
        } catch (Exception e) {
            e.printStackTrace();
        }
        return attrList;
    }


    /**
     * 获取给定模型的 属性List集合(不包括属性设置不展示的)
     *
     * @param modelId
     * @return 排序规则：model_id, show_order, group_id nulls last, group_order, attr_id
     */
    public List<AttrConfig> getConfgLst(String modelId) {
        List<AttrConfig> attrList = null;
        try {
            LinkedHashMap<String, AttrConfig> ma = (LinkedHashMap<String, AttrConfig>) Ehcache.getCache().getAttrConfigCache().get(modelId);
//			HashMap<String, AttrConfig> ma = Ehcache.getCache().getAttrConfigCache().get(modelId);
            if (null == ma || 0 == ma.size()) {
//				ma = new HashMap<String, AttrConfig>();
                ma = new LinkedHashMap<String, AttrConfig>();
                Map<String, String> cond = new HashMap<>();
                cond.put("modelId", modelId);
                attrList = attrConfigDao.queryAttributeListStart(cond);
                for (AttrConfig ac : attrList) {
                    ma.put(ac.getAttrColumn(), ac);
                }
                Ehcache.getCache().getAttrConfigCache().put(modelId, ma);
            } else {
                attrList = new ArrayList<AttrConfig>();
                for (AttrConfig ac : ma.values()) {
                    attrList.add(ac);
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return attrList;
    }

    /**
     * 获取给定模型的属性Map集合
     *
     * @param modelId
     * @return
     */
    public HashMap<String, AttrConfig> getAttrMap(String modelId) {
        LinkedHashMap<String, AttrConfig> ma = null;
//		HashMap<String, AttrConfig> ma = null;
        try {
            ma = (LinkedHashMap<String, AttrConfig>) Ehcache.getCache().getAttrConfigCache().get(modelId);
            if (ma == null) {
//				ma = new HashMap<String, AttrConfig>();
                ma = new LinkedHashMap<String, AttrConfig>();
                Map<String, String> cond = new HashMap<>();
                cond.put("modelId", modelId);
                List<AttrConfig> attrList = attrConfigDao.queryValidAttributeList(cond);
                for (AttrConfig ac : attrList) {
                    ma.put(ac.getAttrColumn(), ac);
                }
                Ehcache.getCache().getAttrConfigCache().put(modelId, ma);
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return ma;
    }

    /**
     * 获取单个 AttrConfig
     *
     * @param modelId 模型ID
     * @param plus    属性ID or 列名
     * @return
     */
    public AttrConfig getAttrConfig(String modelId, String plus) {
        try {
            if (plus == null || "".equals(plus)) {
                throw new RuntimeException("请传入属性ID或列名！");
            } else if (plus.startsWith(TableConst.COLUMNPREFIX)) {
                return this.getAttrMap(modelId).get(plus);
            } else {
                List<AttrConfig> acList = this.getConfgLst(modelId);
                for (AttrConfig attr : acList) {
                    if (plus.equals(attr.getAttrId()))
                        return attr;
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

    /**
     * 级联的属性
     */
    public AttrConfig getCascadeAttrConfig(String modelId, String plus) {
        try {
            if (plus == null || "".equals(plus) || plus.startsWith(TableConst.COLUMNPREFIX)) {
                return null;
            } else {
                List<AttrConfig> acList = this.getAttrList(modelId);
                for (AttrConfig attr : acList) {
                    if (plus.equals(attr.getCascadedAttr()))
                        return attr;
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

    /**
     * 按组获取模型的属性集合
     *
     * @param modelId 给定的模型ID
     * @param groupId 给定的组ID
     * @return
     */
    public List<AttrConfig> getAttrListByGroup(String modelId, String groupId) {
        List<AttrConfig> attrList = new ArrayList<AttrConfig>();
        try {
            List<AttrConfig> acList = this.getAttrList(modelId);
            if (groupId == null) {
                for (AttrConfig attr : acList) {
                    if (attr.getGroupId() == null)
                        attrList.add(attr);
                }
            } else {
                for (AttrConfig attr : acList) {
                    if (groupId.equals(attr.getGroupId()))
                        attrList.add(attr);
                }
            }
            // 屬性排序 (按组内顺序)
            Collections.sort(attrList, new java.util.Comparator<AttrConfig>() {
                @Override
                public int compare(AttrConfig o1, AttrConfig o2) {
                    int sort = o1.getGroupOrder() - o2.getGroupOrder();
//					if(sort==0)
//						sort = o1.getAttrId().compareTo(o2.getAttrId());
                    return sort;
                }
            });
        } catch (Exception e) {
            e.printStackTrace();
        }
        return attrList;
    }

    /*
     * 获取属性组集合
     */
//	public static List<AttrGroup> getGroupList(String modelId){
//		return Ehcache.getCache().getGroupList(modelId);
//	}

    /**
     * 移除模型缓存信息
     */
    public void removeElement(String modelId) {
        Ehcache.getCache().getModelCache().remove(modelId);
        Ehcache.getCache().getColumnsCache().remove(modelId);
        Ehcache.getCache().getAttrConfigCache().remove(modelId);
        Ehcache.getCache().getQueryColsCache().remove(modelId);
    }

    /**
     * 更新模型的缓存
     */
    public void addModel(Model model) {
        Ehcache.getCache().getModelCache().put(model.getId(), model);
    }

    /**
     * 移除属性配置的缓存，等待下次获取时被动更新
     */
    public void removeAttrConfig(String modelId) {
        Ehcache.getCache().getAttrConfigCache().remove(modelId);
    }

    /**
     * 移除模型列的转义 缓存
     */
    public void removeQueryCols(String modelId) {
        Ehcache.getCache().getQueryColsCache().remove(modelId);
    }

    /**
     * 获取给定流程的所有任务节点
     */
    // public List<UserTask> getWfTaskList(String processDefineId) {
    //     return Ehcache.getCache().getWfTaskCache().get(processDefineId);
    // }

    /**
     * 获取给定流程、给定节点的任务对象
     */
    // public UserTask getWfTask(String processDefineId, String activitiId) {
    //     List<UserTask> taskList = Ehcache.getCache().getWfTaskCache().get(processDefineId);
    //     for (UserTask task : taskList) {
    //         if (task.getId().equals(activitiId))
    //             return task;
    //     }
    //     return null;
    // }

}
